home *** CD-ROM | disk | FTP | other *** search
/ Garbo / Garbo.cdr / mac / comm / revrdist.sit / RevRdist / RevRdist src / fileops.c < prev    next >
Encoding:
C/C++ Source or Header  |  1990-06-13  |  9.4 KB  |  411 lines  |  [TEXT/KAHL]

  1. /*
  2.  * fileops.c - routines for misc file/folder operations
  3.  */
  4. #include "RevRdist.h"
  5. #include "dispatch.h"
  6. #include <TransSkelProto.h>
  7. #include <TransDisplayProto.h>
  8.  
  9.  
  10.  
  11. /*
  12.  *=========================================================================
  13.  * createFolder (name, vol, dir, ct) - create a folder
  14.  * entry:    name = string giving folder name
  15.  *            vol = ioVRefNum of volume to create folder in
  16.  *            dir = dirID name is relative to
  17.  *            ct = pointer to optional catalog node whose window information
  18.  *                will be copied to the new folder
  19.  *=========================================================================
  20.  */
  21. OSErr
  22. createFolder (name, vol, dir, ct)
  23.     StringPtr    name;
  24.     Integer        vol;
  25.     Longint        dir;
  26.     cnode_t *    ct;
  27. {
  28.     int                error;
  29.     HParamBlockRec    hpb;
  30.     CInfoPBRec        ci;
  31.  
  32.     error = 0;
  33.     ZERO (hpb);
  34.     hpb.fileParam.ioNamePtr = name;
  35.     hpb.fileParam.ioVRefNum = vol;
  36.     hpb.fileParam.ioDirID = dir;
  37.     error = PBDirCreate (&hpb, false);
  38.     if (error)
  39.     {
  40.         Clue1 = (SP) "\pPBDirCreate";
  41.         goto errexit;
  42.     }
  43.     if (ct)
  44.     {
  45.         ZERO (ci);
  46.         ci.dirInfo.ioVRefNum = vol;
  47.         ci.dirInfo.ioFDirIndex = -1;
  48.         ci.dirInfo.ioDrDirID = hpb.fileParam.ioDirID;
  49.         error = PBGetCatInfo (&ci, false);
  50.         if (error)
  51.         {
  52.             Clue1 = (SP) "\pPBGetCatInfo";
  53.             goto errexit;
  54.         }
  55.         ci.dirInfo.ioDrCrDat = ct->crDate;
  56.         ci.dirInfo.ioDrMdDat = ct->mdDate;
  57.         ci.dirInfo.ioDrUsrWds.frRect = ct->in.d.dinfo.frRect;
  58.         ci.dirInfo.ioDrUsrWds.frView = ct->in.d.dinfo.frView;
  59.         ci.dirInfo.ioDrFndrInfo.frScroll = ct->in.d.frScroll;
  60.         error = PBSetCatInfo (&ci, false);
  61.         if (error)
  62.         {
  63.             Clue1 = (SP) "\pPBSetCatInfo";
  64. errexit:
  65.             ClueID = error;
  66.             Clue0 = (SP) "\pcreateFolder";
  67.         }
  68.     }
  69.     return error;
  70. }
  71.  
  72.  
  73. /*
  74.  *=========================================================================
  75.  * discard (cp,flg) - delete file/folder from client
  76.  * entry:    cp = pointer to client catalog list node
  77.  *            flg = true to log the discard
  78.  *            ClientVol applies to catalog
  79.  * returns:    0 on success, else OSErr
  80.  *=========================================================================
  81.  */
  82. OSErr
  83. discard (cp, flg)
  84. register cnode_t *    cp;
  85. Boolean            flg;
  86. {
  87.     OSErr            error;
  88.     HParamBlockRec    pb;                    /* PBHDelete param block */
  89.  
  90.     if (flg)
  91.         notice (L_DISCARD, cp->name, nil);
  92.     if (Flags & DB_LISTONLY)
  93.         return 0;
  94.     /*
  95.      * If the file is locked, we need to unlock it first
  96.      */
  97.     if (cp->attrib & fLocked)
  98.         error = unlock (cp);
  99.     ZERO (pb);
  100.     pb.fileParam.ioNamePtr = cp->name;
  101.     pb.fileParam.ioVRefNum = ClientVol;
  102.     pb.fileParam.ioDirID = cp->parID;
  103.     error = PBHDelete (&pb, false);
  104.     if (error && error != fnfErr)
  105.     {
  106.         ClueID = error;
  107.         if (flg)
  108.             notice (L_SYS, (SP) "\pdiscard", (SP) "\pPBDelete", nil);
  109.     }
  110.     else
  111.         if (flg)
  112.             statMsgClr ();
  113.     return error;
  114. }
  115.  
  116.  
  117.  
  118.  
  119. /*
  120.  *=========================================================================
  121.  * emptyFolder (ap, func) - empty client folder given by catalog list entry
  122.  * entry:    first param = pointer to catalog list node for client folder
  123.  *            second param = pointer to function to call for each entry
  124.  *                in folder to see if it should be deleted.
  125.  *                = nil to always delete
  126.  *            ClientVol = VRefNum of client volume
  127.  * returns:    0 if folder emptied, else <> 0
  128.  *=========================================================================
  129.  */
  130. DISPATCHED (emptyFolder)
  131. {
  132.     struct    lm
  133.     {
  134.         frame_t            f;
  135.         cnode_t *        ap;            /* copy of first arg */
  136.         ProcPtr            func;        /* copy of second arg */
  137.         cnode_t *        fp;            /* head of catalog list for folder */
  138.         cnode_t *        cp;            /* ptr to current entry in fp */
  139.         Boolean            rej;        /* true once filter rejects */
  140.     };
  141.     typedef struct lm    lm_t;
  142.     register lm_t *        m;
  143.     register cnode_t *    cp;            /* working copy of m->cp */
  144.     OSErr                error;
  145.     Ptr                    paramv[2];
  146.     short                result;
  147.     
  148.     m = *(lm_t **)fh;
  149.     result = request;
  150.     error = 0;
  151.     switch (request)
  152.     {
  153.     case R_INIT:
  154.         if (ClueID = resizeFrame (fh, sizeof (lm_t)))
  155.             return R_ERROR;
  156.         m = *(lm_t **)fh;
  157.         m->ap = (cnode_t *)argv[0];
  158.         m->func = (ProcPtr)argv[1];
  159.         m->f.state = 1;
  160.         return R_CONT;
  161.         
  162.     case R_CONT:
  163.         switch (m->f.state)
  164.         {
  165.         case 1:
  166.             notice (L_DOEMPTY, m->ap->name, nil);
  167.             if (m->ap->attrib & fLocked)
  168.             {
  169.                 if (error = unlock (m->ap))
  170.                 {
  171.                     paramv[0] = (Ptr)error;
  172.                     return (popCall (R_CONT, paramv));
  173.                 }
  174.             }
  175.             cp = listFolder (ClientVol, m->ap->dirID);
  176.             if (cp == nil)
  177.             {
  178.                 paramv[0] = 0;
  179.                 return (popCall (R_CONT, paramv));
  180.             }
  181.             m->fp = m->cp = cp;
  182.             m->f.state = 2;
  183.             return R_CONT;
  184.         case 2:
  185.             /*
  186.              * For each iteration in state 2, we discard one entry,
  187.              * either a file or a folder
  188.              */
  189.             cp = m->cp;
  190.             if (!cp)
  191.                 break;                /* done with folder, exit */
  192.             m->cp = cp->link;        /* assume will go on */
  193.             if (m->func && !(*m->func)(cp))
  194.             {
  195.                 m->rej = true;        /* if filter rejects entry */
  196.                 return R_CONT;
  197.             }
  198.             if (cp->ctype == C_FOLDER)
  199.             {
  200.                 /*
  201.                  * Use ourselves to empty a folder
  202.                  */
  203.                 m->cp = cp;            /* back up to us again */
  204.                 m->f.state = 3;
  205.                 paramv[0] = (Ptr) cp;
  206.                 paramv[1] = (Ptr) m->func;
  207.                 result = pushCall (emptyFolder, paramv);
  208.                 if (result == R_CONT)
  209.                     Depth++;
  210.                 return result;
  211.             }
  212.             error = discard(cp, true);
  213.             if (error && error != fnfErr)
  214.                 m->rej = true;
  215.             return R_CONT;
  216.         case 3:
  217.             /*
  218.              * Here after folder emptied
  219.              */
  220.             Depth--;
  221.             cp = m->cp;
  222.             m->cp = cp->link;
  223.             m->f.state = 2;
  224.             if (argv[0])
  225.                 m->rej = true;    /* folder could not be emptied */
  226.             else
  227.             {
  228.                 if ((error = discard (cp, true)) && error != fnfErr)
  229.                     m->rej = true;
  230.             }
  231.             return R_CONT;
  232.         } /* end of R_CONT state switch */
  233.         break;
  234.     /*
  235.      * R_QUIT and R_BACKOUT just fall through
  236.      */
  237.     }
  238.     paramv[0] = nil;
  239.     if (GetHandleSize ((Handle)fh) >= sizeof (lm_t))
  240.     {
  241.         freeList (m->fp);
  242.         paramv[0] = (Ptr)&m->rej;
  243.     }
  244.     statMsgClr ();
  245.     return (popCall (result, paramv));
  246. }
  247.  
  248.  
  249.  
  250. /*
  251.  *=========================================================================
  252.  * relock (cp) - set the finder locked bit on a client file/folder
  253.  * entry:    cp = pointer to catalog list entry for file/folder
  254.  *            ClientVol set
  255.  * returns:    OSErr
  256.  *=========================================================================
  257.  */
  258. OSErr
  259. relock (cp)
  260. register cnode_t *    cp;
  261. {
  262.     HParamBlockRec    pb;
  263.     OSErr        error;
  264.  
  265.     ZERO (pb);
  266.     pb.fileParam.ioNamePtr = cp->name;
  267.     pb.fileParam.ioVRefNum = ClientVol;
  268.     pb.fileParam.ioDirID = cp->parID;
  269.     error = PBHSetFLock (&pb, false);
  270.     if (error && error != fnfErr)
  271.     {
  272.         Clue1 = (SP) "\pPBHSetFLock";
  273.         Clue0 = (SP) "relock";
  274.         return error;
  275.     }
  276.     cp->attrib |= fLocked;
  277.     return error;
  278. }
  279.  
  280.  
  281.  
  282. /*
  283.  *=========================================================================
  284.  * unlock (cp) - clear the finder locked bit on a client file/folder
  285.  * entry:    cp = pointer to catalog list entry for file/folder
  286.  *            ClientVol set
  287.  * returns:    OSErr
  288.  *=========================================================================
  289.  */
  290. OSErr
  291. unlock (cp)
  292. register cnode_t *    cp;
  293. {
  294.     HParamBlockRec    pb;
  295.     OSErr        error;
  296.  
  297.     ZERO (pb);
  298.     pb.fileParam.ioNamePtr = cp->name;
  299.     pb.fileParam.ioVRefNum = ClientVol;
  300.     pb.fileParam.ioDirID = cp->parID;
  301.     error = PBHRstFLock (&pb, false);
  302.     if (error && error != fnfErr)
  303.     {
  304.         Clue1 = (SP) "\pPBHRstFLock";
  305.         Clue0 = (SP) "unlock";
  306.         return error;
  307.     }
  308.     cp->attrib &= ~fLocked;
  309.     return error;
  310. }
  311.  
  312.  
  313. /*
  314.  *=========================================================================
  315.  * verifyBlessed () - check client "Blessed" folder
  316.  * entry:    ClientVol set
  317.  *=========================================================================
  318.  */
  319. void
  320. verifyBlessed ()
  321. {
  322.     OSErr            error;
  323.     Longint            dirID;            /* dir ID of blessed folder */
  324.     long            saveflags;        /* copy of Flags */
  325.     CInfoPBRec        ci;                /* for PBGetCatInfo */
  326.     HParamBlockRec    pb;                /* for PBHGetVInfo */
  327.     Str255            fs, vs;            /* file and volume name strings */
  328.  
  329.     /*
  330.      * Get info about client volume.
  331.      */
  332.     Clue0 = (SP)"\pverifyBlessed";
  333.     ZERO (pb);
  334.     vs[0] = 0;
  335.     pb.volumeParam.ioNamePtr = vs;
  336.     pb.volumeParam.ioVRefNum = ClientVol;
  337.     pb.volumeParam.ioVolIndex = -1;
  338.     Clue1 = (SP)"\pPBHGetVInfo";
  339.     if (error = PBHGetVInfo (&pb, false))
  340.         goto syserr;
  341.     dirID = pb.volumeParam.ioVFndrInfo[0];
  342.     if (dirID == 0)
  343.     {
  344.         /*
  345.          * No blessed folder set yet.  See if there is one with right name
  346.          */
  347.         fs[0] = 0;
  348.         GetIndString (fs, NAME_STR, NAME_FOLDER);
  349.         if (fs[0] == 0)
  350.             return;
  351.         ZERO (ci);
  352.         ci.dirInfo.ioNamePtr = fs;
  353.         ci.dirInfo.ioVRefNum = ClientVol;
  354.         Clue1 = (SP)"\pPBGetCatInfo";
  355.         if (error = PBGetCatInfo (&ci, false))
  356.             goto cantboot;
  357.         dirID = ci.dirInfo.ioDrDirID;
  358.         /*
  359.          * Make it the Blessed folder, which may be presumptuous
  360.          */
  361.         if (Flags & DB_VERBOSE)
  362.             notice (L_BLESSED, nil);
  363.         if ((Flags & DB_LISTONLY) == 0)
  364.         {
  365.             pb.volumeParam.ioVFndrInfo[0] = dirID;
  366.             pb.volumeParam.ioVFndrInfo[1] = dirID;
  367.             pb.volumeParam.ioNamePtr = 0;
  368.             Clue1 = (SP)"\pPBSetVInfo";
  369.             if (error = PBSetVInfo (&pb, false))
  370.                 goto syserr;
  371.         }
  372.     }
  373.     /*
  374.      * Check Blessed folder for System file and Finder
  375.      */
  376.     fs[0] = 0;
  377.     GetIndString (fs, NAME_STR, NAME_SYSTEM);
  378.     if (fs[0] == 0)
  379.         return;
  380.     ZERO (ci);
  381.     ci.hFileInfo.ioNamePtr = fs;
  382.     ci.hFileInfo.ioVRefNum = ClientVol;
  383.     ci.hFileInfo.ioDirID = dirID;
  384.     Clue1 = (SP)"\pPBGetCatInfo";
  385.     if (error = PBGetCatInfo (&ci, false))
  386.         goto cantboot;
  387.     fs[0] = 0;
  388.     GetIndString (fs, NAME_STR, NAME_FINDER);
  389.     if (fs[0] == 0)
  390.         return;
  391.     ci.hFileInfo.ioDirID = dirID;
  392.     ci.hFileInfo.ioFDirIndex = 0;
  393.     if (error = PBGetCatInfo (&ci, false))
  394.         goto cantboot;
  395.     pb.volumeParam.ioNamePtr = 0;
  396.     (void) PBFlushVol ((ParmBlkPtr)&pb, false);
  397.     return;
  398.     
  399. cantboot:
  400.     if (error == fnfErr)
  401.     {
  402.         saveflags = Flags;
  403.         Flags &= ~DB_STARTUP;
  404.         warning (E_BLESSED, vs, fs, nil);
  405.         Flags = saveflags;
  406.         return;
  407.     }
  408. syserr:
  409.     ClueID = error;
  410.     panic (true, E_SYS, nil);
  411. }